package org.groupg.practice;

import cn.hutool.core.lang.Console;
import cn.hutool.core.util.RandomUtil;
import io.github.resilience4j.circuitbreaker.CircuitBreaker;
import io.github.resilience4j.circuitbreaker.CircuitBreakerConfig;
import io.github.resilience4j.retry.Retry;
import io.github.resilience4j.retry.RetryConfig;
import java.time.Duration;

public class SingleThreadExample {

    // 模拟可能失败的服务
    static class UnstableService {
        private int attempt = 0;

        String process() {
            attempt++;
            // 模拟失败逻辑：前两次失败，第三次成功
            if (attempt <= 2) {
                throw new RuntimeException("Service unavailable");
            }
            return "Processed successfully";
        }
    }

    public static void main(String[] args) {
        // 配置断路器：5次调用中有50%失败时打开
        CircuitBreakerConfig cbConfig = CircuitBreakerConfig.custom()
                .failureRateThreshold(50)
                .slidingWindowSize(5)
                .waitDurationInOpenState(Duration.ofSeconds(10))
                .build();
        CircuitBreaker circuitBreaker = CircuitBreaker.of("myCircuitBreaker", cbConfig);

        // 配置重试：最多重试3次，每次间隔500ms
        RetryConfig retryConfig = RetryConfig.custom()
                .maxAttempts(3)
                .waitDuration(Duration.ofMillis(500))
                .retryOnException((e)->{
                    boolean result = RandomUtil.randomBoolean();;
                    Console.log(result);
                    return result;
                })
                .build();
        Retry retry = Retry.of("myRetry", retryConfig);

        UnstableService service = new UnstableService();

        // 组合断路器+重试
        Runnable decoratedRunnable = CircuitBreaker.decorateRunnable(
                circuitBreaker,
                Retry.decorateRunnable(
                        retry,
                        () -> System.out.println("Result: " + service.process())
                )
        );

        // 执行（会触发两次重试）
        try {
            decoratedRunnable.run();
        } catch (Exception e) {
            System.err.println("Final failure: " + e.getMessage());
        }
    }
}